#!/usr/bin/python2.5
import time
from time import sleep, localtime, strftime
import sys
import httplib, urllib

# TODO
# - Cleanup the code [PARTLY DONE 2008-04-05]
# - Generate more triggers & settings
#   * update position when moved x meters
#   * update position when direction changes
# - Logging to a file
# - Automatic generation of GPX file
# - make current triggers work better
#   * do not send location if it hasnt changed
#     (need to drop couple of decimals)
# - make boozeman drink all of his whiskey
#   as he has too many freaking IDEAS!


class YouLocUpdater:
	version = 0.41
	user_key = ""
	updateInterval = 5
	gps_device = ""
	lastLat = None
	lastLong = None
	lastTime = time.time() - 100
	connected = 0

	def __init__(self):
		print "__   ___     ______"
		print "\\ \\ / / |    | ___ \\"
		print " \\ V /| |    | |_/ /_ __  _   _"
		print "  \\ / | |    |  __/| '_ \\| | | |"
		print "  | | | |____| |  _| |_) | |_| |"
		print "  \\_/ \\_____/\\_| (_) .__/ \\__, |"
		print "   YouLocPython    | |     __/ |"
		print "   %0.2fa           |_|    |___/" % (self.version)

	def logger(self, message):
			print "[%s] %s" % ( strftime("%H:%M:%S",localtime()), message.strip() )
		
	def postData(self,time,lat,long):
		self.logger("Opening HTTP-connection")
		try:
			conn = httplib.HTTPConnection("proto.youloc.net:80")
			url = "/self.logger.php?imei=%s&time=%s&lat=%s&lon=%s" % (self.user_key, time, lat, long)
			conn.request("GET", url)
			self.logger("Posted: %s, %s" % (lat, long))   
			response = conn.getresponse()
			data = response.read()
		except:
			etype = sys.exc_type
			try:
				ename = etype.__name__ 
			except AttributeError:
				ename = etype
			print strftime("[%H:%M:%S]",localtime()),"ERROR:", str(ename) + ":", sys.exc_value
		finally:
			conn.close()
			self.logger("Closed HTTP-connection")

	def parseData(self, data):
		d = data.split( ',' )
		return (d[1], d[2],d[3], d[4],d[5] )

	def parseLatLon(self, latitude,longitude,northsouth,eastwest):
		latitude_in=float(latitude)
		longitude_in=float(longitude)
		if northsouth == 'S':
			latitude_in = -latitude_in
		if eastwest == 'W':
			longitude_in = -longitude_in
		
		latitude_degrees = int(latitude_in/100)
		latitude_minutes = latitude_in - latitude_degrees*100
		
		longitude_degrees = int(longitude_in/100)
		longitude_minutes = longitude_in - longitude_degrees*100
		
		latitude = latitude_degrees + (latitude_minutes/60)
		longitude = longitude_degrees + (longitude_minutes/60)
		return (latitude,longitude)   

	def start(self):
		error = 0
		if (self.user_key == ""):
			self.logger("ERROR: You need to define user_key")
			error = 1
		if (self.updateInterval <= 0):
			self.logger("WARNING: You havent set update interval, if self is not set, position will not be updated to server")
			
		if (self.gps_device == ""):
			self.logger("ERROR: You havent specified a gps device, we cant continue without it")
			error = 1
			
		if (error):
			sys.exit()
			
		while (True):
			try: 
				self.logger('Trying to open GPS-device')
				f = open(self.gps_device)
				self.logger('GPS-device opened')
				try:
					self.logger('Receiving data from satellite')
					for data in f:
						if (self.connected == 0):
							self.logger(data)
						if(data[0:6] == '$GPGGA' ):
							(utc,latitude, northsouth, longitude, eastwest) = self.parseData( data )
							curTime = time.time()
							if( latitude != "" and longitude != "" and ( latitude != self.lastLat or longitude != self.lastLong ) and curTime > self.lastTime + self.updateInterval):
								if (self.connected == 0 ):
									self.logger("GPS-receiver got fix from satellite")
									self.connected = 1
								(latitude, longitude) = self.parseLatLon(latitude,longitude,northsouth, eastwest)
								timeOfFix = time.strftime("%H:%M:%S", time.strptime(utc.split(".")[0],"%H%M%S"))
								self.lastLat = latitude
								self.lastLong = longitude
								self.lastTime = curTime
								self.postData(curTime,latitude,longitude)

				finally:
					try:
						f.close()
						self.logger("GPS-device closed")
					except AttributeError, v:
						print v

			except:
				etype = sys.exc_type
				try:
					ename = etype.__name__
				except AttributeError:
					ename = etype
				print strftime("[%H:%M:%S]",localtime()),"ERROR:", str(ename) + ":", sys.exc_value
			
				if (str(ename) == "IOError"):
					self.logger("ERROR: GPS-device vanished beneath me! Waiting for 10 seconds before connecting again")
				try:
					sleep(10)
				except KeyboardInterrupt:
					self.logger("User pressed CTRL-C, exiting");
					sys.exit()
				if (str(ename) == "KeyboardInterrupt"):
					self.logger("User pressed CTRL-C, exiting");
					sys.exit()



YLP = YouLocUpdater()
YLP.gps_device = "/dev/tty.NokiaLD-3W-DevB-1"
YLP.user_key = "test_key"
YLP.start()





